我在Yacfe示例中看到了以下函数调用:
Visitor_c.vk_program { Visitor_c.default_visitor_c with Visitor_c.kexpr = (fun (k, bigf) exp -> match Ast_c.unwrap_expr exp with | Binary(e1, Logical (Eq), (((Constant(Int("0")) as _e2),_t),ii)) -> (match Ast_c.get_onlytype_expr e1 with | Some (qu, (Pointer _,_ii)) -> let idzero = Common.tuple_of_list1 ii in idzero.cocci_tag := Ast_cocci.MINUS (Ast_cocci.NoPos, [[null_addon]]), []; | _ -> k exp ) | _ -> k exp ); } ast;
我可以看到一个函数调用,其中记录初始化为第一个参数,并ast
作为第二个参数.
我不熟悉的是表单的语法:
{Visitor_c.default_visitor_c with Visitor_c.kexpr = some_value;}
这意味着什么?我知道记录可以初始化{name=value;name=value;...}
,但是我不熟悉{X with name=value}
,你能告诉我它意味着什么吗?
我在Ocaml手册中找不到关于合法记录值初始化的任何内容,除了以下内容:
6.2.3记录
记录值标记为值的元组.写入的记录值{field1 = v1; ...; fieldn = vn}将值vi与记录字段fieldi相关联,对于i = 1 ... n.当前实现支持最多222-1个字段(4194303字段)的记录.
如果您在答案中提及OCaml手册中的相关部分,我将很高兴.
这有时被称为"记录更新"或"功能更新"或类似的东西.它评估为与X相同类型的新记录,其字段初始化为与X中的字段相同,除了在"with"之后列出的字段,它们被初始化为给定值.
它对于不可变记录很有用,作为一种方便的方法来获取这样的记录并在其上更改一两个东西(在命令式语言中,您通常会改变字段),而不必列出所有未更改的字段.
它在OCaml手册第6.7.3节中描述,向下滚动到"记录",第二段.
对于那些熟悉Haskell,OCaml语法的人
{ expr with field1 = expr1 ; ... ; fieldn = exprn }
与Haskell语法相同
expr { field1 = expr1 , ... , fieldn = exprn }
要更正先前的回复,新记录的类型并不总是与旧记录相同.例如,你可以有类似的东西:
type 'a t = { id : int; value : 'a; } let old_t = { id = 3; value = "foo" } let new_t = { old_t with value = 3 }
因此,old_t
属于类型string t
,而new_t
属于类型int t
.